package cn.juque.systemservice.service.provider;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.juque.common.annotation.HandlerAppException;
import cn.juque.common.base.BaseResponseDTO;
import cn.juque.common.base.PageInfo;
import cn.juque.common.constants.MessageEnum;
import cn.juque.common.thread.BaseOperatorThreadLocal;
import cn.juque.common.utils.ValidatorUtil;
import cn.juque.systemservice.api.dto.dict.*;
import cn.juque.systemservice.api.provider.IDictInfoProvider;
import cn.juque.systemservice.cache.DictInfoCache;
import cn.juque.systemservice.entity.DictInfo;
import cn.juque.systemservice.service.IDictInfoService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;

/**
 * @author JUQUE
 * @version 1.0.0
 * <li>simple-generator</li>
 * <li></li>
 * @date 2022-10-26 17:29:56
 **/
@Slf4j
@Service("dictInfoProvider")
@HandlerAppException
public class DictInfoProviderImpl implements IDictInfoProvider {

    @Resource
    private BaseOperatorThreadLocal baseOperatorThreadLocal;

    @Resource
    private IDictInfoService dictInfoService;

    @Resource
    private DictInfoCache dictInfoCache;

    @Resource
    private ValidatorUtil validatorUtil;

    /**
     * 列表检索
     *
     * @param searchDTO 入参
     * @return List
     */
    @Override
    public BaseResponseDTO<List<DictInfoListDTO>> list(DictInfoSearchDTO searchDTO) {
        this.validatorUtil.checkNotNull(searchDTO);
        PageInfo pageInfo = searchDTO.getPageInfo();
        DictInfo dictInfo = new DictInfo();
        BeanUtil.copyProperties(searchDTO, dictInfo);
        List<DictInfo> infoList;
        if (null == pageInfo) {
            infoList = this.dictInfoService.listInfoWithoutPage(dictInfo);
        } else {
            infoList = this.dictInfoService.listInfoWithPage(pageInfo, dictInfo);
        }
        List<DictInfoListDTO> infoDtoList = BeanUtil.copyToList(infoList, DictInfoListDTO.class);
        return new BaseResponseDTO<>(MessageEnum.OK, infoDtoList, pageInfo);
    }

    /**
     * 详情
     *
     * @param id 主键
     * @return DictInfoDetailDTO
     */
    @Override
    public BaseResponseDTO<DictInfoDetailDTO> detail(String id) {
        DictInfo dictInfo = this.dictInfoService.detail(id);
        DictInfoDetailDTO detailDTO = new DictInfoDetailDTO();
        BeanUtil.copyProperties(dictInfo, detailDTO);
        return new BaseResponseDTO<>(MessageEnum.OK, detailDTO);
    }

    /**
     * 新增
     *
     * @param addDTO 入参
     * @return Boolean
     */
    @Override
    public BaseResponseDTO<Boolean> add(DictInfoAddDTO addDTO) {
        this.validatorUtil.fastValidate(addDTO);
        this.baseOperatorThreadLocal.set(addDTO.getBaseOperator());
        DictInfo dictInfo = new DictInfo();
        BeanUtil.copyProperties(addDTO, dictInfo);
        this.dictInfoService.saveInfo(dictInfo);
        return new BaseResponseDTO<>(MessageEnum.OK, Boolean.TRUE);
    }

    /**
     * 更新
     *
     * @param updateDTO 入参
     * @return Boolean
     */
    @Override
    public BaseResponseDTO<Boolean> update(DictInfoUpdateDTO updateDTO) {
        this.validatorUtil.fastValidate(updateDTO);
        this.baseOperatorThreadLocal.set(updateDTO.getBaseOperator());
        DictInfo dictInfo = new DictInfo();
        BeanUtil.copyProperties(updateDTO, dictInfo);
        this.dictInfoService.updateInfo(dictInfo);
        return new BaseResponseDTO<>(MessageEnum.OK, Boolean.TRUE);
    }

    /**
     * 删除
     *
     * @param req 入参
     * @return Boolean
     */
    @Override
    public BaseResponseDTO<Boolean> delete(DictInfoDeleteDTO req) {
        List<String> infoIdList = req.getIdList();
        this.dictInfoService.deleteInfo(infoIdList);
        return new BaseResponseDTO<>(MessageEnum.OK, Boolean.TRUE);
    }

    /**
     * 根据类别检索字典
     *
     * @param req 入参
     * @return resp
     */
    @Override
    public BaseResponseDTO<List<DictInfoDetailDTO>> getDictListByType(DictSearchByTypeDTO req) {
        List<String> dictType = req.getDictTypeList();
        if (CollUtil.isEmpty(dictType)) {
            return new BaseResponseDTO<>(MessageEnum.OK, CollUtil.newArrayList());
        }
        List<DictInfo> resultList = CollUtil.newArrayList();
        dictType.forEach(t -> {
            List<DictInfo> dictList = this.dictInfoCache.getDictByDictType(t);
            CollUtil.addAll(resultList, CollUtil.isNotEmpty(dictList) ? dictList : CollUtil.newArrayList());
        });
        List<DictInfoDetailDTO> dtoList = BeanUtil.copyToList(resultList, DictInfoDetailDTO.class);
        return new BaseResponseDTO<>(MessageEnum.OK, dtoList);
    }
}
